package com.edu.commons;

import io.jsonwebtoken.*;

import java.util.Date;
import java.util.HashMap;
import java.util.Map;

/**
 * @ProjectName: summer-project
 * @Titile: JWTUtils
 * @Author: Lucky
 * @Description: JWT工具类型
 */
public class JWTUtils {
    //token的有效期，过了有效期后，token（令牌）就会失效，要重新登录
    private static  long TOKEN_EXP_TIME = 7*24*60*60*1000;
    //签名，要定期更换，保证安全
    private static String TOKEN_SIGNS = "kflawad%&%#!";

    /**
     * 生成token的方法
     * @param empVO 员工信息
     * @return 身份字符串信息
     */
    public static String generateToken(EmpVO empVO){
        //主体：每个token都需要一个主体，这个主体有可能是人，有可能是机器/设备/终端
        String subject = empVO.getEmpName();
        //当前时间
        Date now = new Date();
        //租约到期时间=当前时间+过期时间  毫秒数
        long expireTime = now.getTime() + TOKEN_EXP_TIME;
        //创建过期时间
        Date exp = new Date(expireTime);
        //生成token
        String token = Jwts.builder().setSubject(subject) //设置主体
                .setIssuedAt(now) //设置当前时间
                .setExpiration(exp) //设置过期时间
                .claim("subId", empVO.getEmpId()) // id
                .claim("subName",empVO.getEmpName()) //员工名称
                .signWith(SignatureAlgorithm.HS256, TOKEN_SIGNS) //算法+签名
                .compact();
        return token;
    }

    /**
     * 校验token
     * @param token 身份信息
     * @return 身份信息
     */
    public static Claims verifyToken(String token) {
        //Claims就是一个容器，用来装员工身份信息的
        Claims claims = null;
        try {
            //解析token
            claims = Jwts.parser().setSigningKey(TOKEN_SIGNS)//设置签名
                    .parseClaimsJws(token) //设置解析的token，token自带算法
                    .getBody();//获取负载
        } catch (ExpiredJwtException e) {
            throw new ServiceException(ServiceCode.ERROR_TOKEN_EXPIRE,"解析token异常:token已经失效");
        } catch (UnsupportedJwtException e) {
            throw new ServiceException(ServiceCode.ERROR_TOKEN_INVALID,"解析token异常:不支持的token解析");
        } catch (MalformedJwtException e) {
            throw new ServiceException(ServiceCode.ERROR_TOKEN_INVALID,"解析token异常:非法token格式");
        } catch (SignatureException e) {
            throw new ServiceException(ServiceCode.ERROR_TOKEN_INVALID,"解析token异常：token的签名不合法");
        } catch (IllegalArgumentException e) {
            throw new ServiceException(ServiceCode.ERROR_TOKEN_INVALID,"解析token异常：非法token参数");
        }
        return claims;
    }

    /**
     * 解析token
     * @param token 员工的身份字符串
     * @return 员工对象
     */
    public static EmpVO parseToken(String token){
        //校验token
        Claims claims = verifyToken(token);
        //获取员工的id
        Integer empId = Integer.valueOf(claims.get("subId").toString());
        //获取员工的名称
        String empName = claims.get("subName").toString();
        EmpVO empVO = new EmpVO();
        empVO.setEmpId(empId);
        empVO.setEmpName(empName);
        return empVO;
    }



    public static void main(String[] args) {

       /* EmpVO empVO = new EmpVO();
        empVO.setEmpId(1001);
        empVO.setEmpName("admin");
        //生成token
        String token = generateToken(empVO);
        System.out.println(token);*/

       /* String token = "eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJhZG1pbiIsImlhdCI6MTcyNDYZODk5MywiZXhwIjoxNzI1MjQzNzkzLCJzdWJJZCI6MTAwMSwic3ViTmFtZSI6ImFkbWluIn0.x0NGrjAjnHhUVZgNPB9MfQiqb9sezHaaHmT1kpU__Tw";
        Claims claims = JWTUtils.verifyToken(token);
        System.out.println(claims.getSubject());*/
        String token = "eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJhZG1pbiIsImlhdCI6MTcyNDYzODk5MywiZXhwIjoxNzI1MjQzNzkzLCJzdWJJZCI6MTAwMSwic3ViTmFtZSI6ImFkbWluIn0.x0NGrjAjnHhUVZgNPB9MfQiqb9sezHaaHmT1kpU__Tw";
        EmpVO empVO = parseToken(token);
        System.out.println(empVO);
    }
}
